---
title: Customer Support Email Generator
description: Learn how to build an intelligent customer support agent that generates personalized email responses
---

<Card
title="Live example"
href="https://app.latitude.so/share/d/e9b20d49-45af-430f-8f4b-cb5b3d8dfc57"
arrow="true"
cta="Copy to your Latitude">
You can play with this example in the Latitude Playground.
</Card>

## Overview

In this example, we will create a Dynamic Customer Support Email Generator that can analyze customer queries, gather relevant customer information, and generate personalized, professional email responses. The agent uses subagents to handle different aspects of customer support efficiently.

## Multi-Agent Architecture

The system uses specialized subagents for different responsibilities:

- **main**: Orchestrates the process and makes decisions
- **customer_researcher**: Gathers customer data and context
- **email_composer**: Creates the actual email response

<Note>
All the tools used in the sub-agents have to be defined in the main prompt.
</Note>

## The prompts

<CodeGroup>
```markdown main
---
provider: google
model: gemini-1.5-flash
type: agent
tools:
  - get_customer_details:
      description: Retrieves customer account information
      parameters:
        type: object
        properties:
          email:
            type: string
            description: Customer email address
        required:
          - email
  - get_order_history:
      description: Gets recent order history for the customer
      parameters:
        type: object
        properties:
          customer_id:
            type: string
            description: Customer ID
        required:
          - customer_id
  - check_known_issues:
      description: Checks for known issues related to the query
      parameters:
        type: object
        properties:
          issue_keywords:
            type: array
            items:
              type: string
            description: Keywords from the customer query
        required:
          - issue_keywords
agents:
  - customer_researcher
  - email_composer
temperature: 0.3
schema:
  type: object
  properties:
    needs_clarification:
      type: boolean
      description: Whether the query needs clarification from the customer
    clarification_questions:
      type: array
      items:
        type: string
      description: Questions to ask the customer for clarification
    email_response:
      type: object
      properties:
        subject:
          type: string
          description: Email subject line
        body:
          type: string
          description: Email body content
      description: The generated email response
  required:
    - needs_clarification
---

You're an intelligent customer support coordinator. Your task is to analyze customer queries and generate appropriate email responses

You have two specialized agents available:
- A customer researcher that can gather customer information and context
- An email composer that creates professional, personalized responses

You must proceed with the following steps, one message at a time:
- Analyze the customer query to understand the issue and sentiment
- Determine if you need more information about the customer or their issue
- If the query is unclear or missing context, ask clarifying questions
- Use the customer researcher to gather relevant customer information
- Use the email composer to create a personalized response
- Review the response for tone, accuracy, and completeness

Handle edge cases like:
- Angry or frustrated customers (use empathetic tone)
- Technical issues (gather specific details)
- Billing inquiries (verify account information)
- Feature requests (acknowledge and route appropriately)

<user>
Customer Email: {{ customer_email }}
Customer Query: {{ customer_query }}
Priority Level: {{ priority_level }}
</user>

First, analyze the customer query and determine what information you need.
```
```markdown customer_researcher
---
provider: OpenAI
model: gpt-4.1
type: agent
description: Researches customer information and gathers relevant context for support queries
---

You're a customer research specialist. Your job is to gather comprehensive information about customers and their issues to enable personalized support.

For each research request, you should:
1. Extract the customer email and any identifiers from the query
2. Gather customer account details and history
3. Check for known issues or patterns related to their query
4. Look for previous support interactions
5. Identify the customer's subscription level or account type
6. Note any special circumstances (VIP customer, recent issues, etc.)

Provide a detailed research report including:
- Customer profile and account status
- Relevant order/subscription history
- Known issues that might be related
- Recommended approach based on customer history
- Any red flags or special considerations

<user>
{{ research_request }}
</user>

Use all available tools to gather comprehensive customer information.
```
```markdown email_composer
---
provider: anthropic
model: claude-3-sonnet-latest
type: agent
description: Composes professional, personalized customer support emails
temperature: 0.4
schema:
  type: object
  properties:
    subject:
      type: string
      description: Professional email subject line
    body:
      type: string
      description: Complete email body with proper formatting
    tone_analysis:
      type: string
      description: Analysis of the tone used in the response
    personalization_elements:
      type: array
      items:
        type: string
      description: Elements that make this response personalized
  required:
    - subject
    - body
    - tone_analysis
---

You're an expert email composer specializing in customer support communications. You create professional, empathetic, and personalized email responses.

Your email composition process:
1. Analyze the customer's emotional state and adjust tone accordingly
2. Use customer information to personalize the response
3. Address the specific issue with clear, actionable solutions
4. Include relevant account details when appropriate
5. Set proper expectations for resolution timelines
6. End with appropriate next steps and contact information

Email guidelines:
- Use the customer's name when available
- Reference specific account details or order numbers
- Match the urgency level to the customer's concern
- For technical issues: provide step-by-step solutions
- For billing issues: be precise about charges and dates
- For complaints: acknowledge, empathize, and provide solutions
- Always include a clear call-to-action

Tone variations:
- Standard: Professional and helpful
- Urgent: Immediate attention with expedited solutions
- Empathetic: Extra care for frustrated customers
- Technical: Detailed explanations for complex issues

<user>
Customer Information: {{ customer_info }}
Issue Details: {{ issue_details }}
Tone Required: {{ tone_required }}
</user>

Compose a professional email response using the provided information.
```
</CodeGroup>

## Breakdown

Let's break down the example step by step to understand how it works.

#### Customer Context Gathering

The customer researcher agent uses custom tools to fetch relevant information:

```markdown
- get_customer_details: Retrieves account information
- get_order_history: Gets purchase history
- check_known_issues: Identifies related problems
```

#### Intelligent Query Analysis

The main agent analyzes queries for:

- Emotional sentiment (angry, confused, urgent)
- Issue type (technical, billing, feature request)
- Information completeness
- Priority level

#### Personalized Response Generation

The email composer creates responses that:

- Use customer-specific information
- Match appropriate tone and urgency
- Include relevant account details
- Provide actionable solutions

#### Structured Output

Uses JSON schema to ensure consistent response format with subject, body, and metadata.

### Why This Multi-Agent Approach Works

Similar to the [Deep Search example](/examples/cases/deep-search), separating responsibilities prevents context bloat and improves performance:

1. **Customer researcher** focuses solely on data gathering
2. **Email composer** specializes in communication
3. **Main coordinator** handles decision-making and orchestration

This prevents any single agent from becoming overloaded with too many responsibilities while maintaining conversation context efficiency.

Looking at the prompts I implemented in the previous conversation, I chose different LLM providers strategically based on their specific strengths and the requirements of each component.

## Code

You can play with this example using the Latitude SDK.

<CodeGroup>
````typescript Typescript
import { Latitude } from '@latitude-data/sdk'

type Tools = {
  get_customer_details: { email: string }
  get_order_history: { customer_id: string }
  check_known_issues: { issue_keywords: string[] }
}

async function run() {
  const sdk = new Latitude(process.env.LATITUDE_API_KEY, {
    projectId: Number(process.env.PROJECT_ID),
    versionUuid: 'live',
  })

  const response = await sdk.prompts.run<Tools>('customer-support-email/main', {
    parameters: {
      customer_email: 'johndoe@gmail.com',
      customer_query: 'My order is delayed and I want to know the status.',
      priority_level: 'urgent',
    },
    tools: {
      get_customer_details: async ({ email }) => {
        return {
          email,
          name: 'John',
          last_name: 'Doe',
          customer_id: '12345',
        }
      },
      get_order_history: async ({ customer_id }) => {
        return {
          customer_id,
          orders: [
            {
              name: 'Nike Air Max 270',
              status: 'Delivered',
              date: '2023-01-01',
            },
            {
              name: 'Adidas Ultraboost',
              status: 'In Transit',
              date: '2023-02-01',
            },
          ],
        }
      },
      check_known_issues: async ({ issue_keywords }) => {
        if (issue_keywords.length === 0) {
          return { issues: [] }
        }

        if (issue_keywords.includes('delay')) {
          return {
            issues: [
              {
                description:
                  'Known issue with delayed shipments due to supply chain disruptions.',
                severity: 'high',
              },
            ],
          }
        }

        return { issues: [] }
      },
    },
  })

  console.log('RESPONSE', JSON.stringify(response, null, 2))
}

run()
````
</CodeGroup>

## Provider Selection Rationale

<AccordionGroup>
  <Accordion title="Main coordinator - Google Gemini Flash">
    1. **Fast Performance**: Designed for quick coordination tasks.
    2. **Cost Effective**: Competitive pricing for simple tasks.
    3. **JSON Support**: Good structured output capabilities
  </Accordion>

  <Accordion title="Customer researcher - OpenAI GPT-4.1">
    1. **Tool Integration**: OpenAI has excellent tool calling capabilities and strict compatibility mode for reliable function execution
    2. **Data Processing**: GPT-4o excels at analyzing and synthesizing information from multiple sources
    3. **Reasoning**: Better at complex reasoning tasks required for customer data analysis
  </Accordion>

  <Accordion title="Email composer - Anthropic Claude Sonnet">
    1. **Writing Quality**: Anthropic models are particularly strong at generating high-quality, nuanced text
    2. **Tone Control**: Superior at maintaining consistent professional tone and empathy
    3. **Temperature**: Used `temperature: 0.4` for creative but controlled email generation
  </Accordion>
</AccordionGroup>

### Strategic Benefits

This multi-provider strategy optimizes for:

- **Cost**: Using cheaper models for coordination, expensive models only where needed
- **Performance**: Leveraging each provider's strengths (OpenAI for tools, Anthropic for writing)
- **Reliability**: Distributing risk across multiple providers
- **Quality**: Matching model capabilities to specific task requirements

<Warning>This rationale might vary with the past of time because provider capabilities and pricing change frequently. We recomend to [evaluate your prompts](/guides/evaluations/overview)</Warning>
<Info>
Using Latitude is easy to switch between providers if needed. If you find that one provider's model is not performing as expected, you can quickly change the model in the prompt configuration without rewriting the entire agent logic. You can create your own providers check [provider documentation](/guides/getting-started/providers) for more information.
</Info>

## Resources

- [Customer Support Best Practices](/guides/prompt-manager/prompt-best-practices) - Learn more about effective customer support prompting
- [Custom Tools](/guides/prompt-manager/tools) - How to integrate with customer databases and CRM systems
- [Tool call SDK example](/examples/sdk/run-prompt-with-tools) - A simple example of how to run a prompt with tools with Latitude SDK.
- [JSON Schema Output](/guides/prompt-manager/json-output) - Ensuring consistent response formatting
- [Configuring providers](/guides/getting-started/providers) - How to configure and use different LLM providers in Latitude
